
package thelife;

import java.awt.*;
import java.awt.event.*;
import java.util.Timer;
import java.util.logging.Level;
import java.util.logging.Logger;
import javax.swing.ButtonGroup;
import javax.swing.JButton;
import javax.swing.JFrame;
import javax.swing.JRadioButton;


/**
 *
 * @author Paweł Młynarczyk <zwarios@gmail.com>
 * @author Sebastian Węc <sebastian.wec@gmail.com>
 */
public class Window extends JFrame implements ActionListener, Runnable {
    Colony colony;
    Matrix m;
    JButton clear;
    JButton randomize;
    JButton speedUp;
    JButton speedDown;
    JButton playBack;
    
    JRadioButton glider;
    JRadioButton smallExploder;
    JRadioButton exploder;
//    JRadioButton gosperGliderGun;
    ButtonGroup radioGroup;
    
    int speed = 200;
    boolean play = false;
    
    Window(Matrix m){        
        this.setBounds(100, 100, 520, 600);
        this.setLayout(null);
        this.m = m;
        colony = new Colony(m);
        add(colony);
        colony.setBounds(0, 0, 500, 500);
        colony.repaint();
        
        clear = new JButton("Wyczyść");
        randomize = new JButton("Losuj");
        speedUp = new JButton("+");
        speedDown = new JButton("-");
        playBack = new JButton("|>");
        clear.addActionListener(this);
        randomize.addActionListener(this);
        speedUp.addActionListener(this);
        speedDown.addActionListener(this);
        playBack.addActionListener(this);
        add(clear);
        add(randomize);
        add(speedUp);
        add(speedDown);
        add(playBack);
        clear.setBounds(10, 510, 90, 40);
        randomize.setBounds(100, 510, 90, 40);
        speedUp.setBounds(400, 510, 50, 40);
        speedDown.setBounds(450, 510, 50, 40);
        playBack.setBounds(350, 510, 50, 40);
        
        glider = new JRadioButton("Glider");
        smallExploder = new JRadioButton("Small Exploder");
        exploder = new JRadioButton("Exploder");
//        gosperGliderGun = new JRadioButton("Gosper Glider Gun");
        
        glider.addActionListener(this);
        smallExploder.addActionListener(this);
        exploder.addActionListener(this);
//        gosperGliderGun.addActionListener(this);     
        
        radioGroup = new ButtonGroup();
        add(glider);
        glider.setBounds(200, 505, 150, 10);
        add(smallExploder);
        smallExploder.setBounds(200, 520, 150, 10);
        add(exploder);
        exploder.setBounds(200, 535, 150, 10);
//        add(gosperGliderGun);
//        gosperGliderGun.setBounds(200, 550, 150, 10);
        
        radioGroup.add(glider);
        radioGroup.add(smallExploder);
        radioGroup.add(exploder);
//        radioGroup.add(gosperGliderGun);
          
        setTitle("Symulacja sztucznego życia na przykładzie sieci komórkowej");
        setVisible(true);
    }
    void repaintColony(){
        colony.repaint();
    }

    @Override
    public void actionPerformed(ActionEvent e) {
        if(e.getSource().equals(clear)){
            m.clear();
        }else if(e.getSource().equals(randomize)){
            m.randomize();
        } else if(e.getSource().equals(speedUp)){
            speed = speed > 30 ? speed - 10 : 30;
            System.out.println(speed);
        } else if(e.getSource().equals(speedDown)){
            speed = speed < 400 ? speed + 10 : 400;
            System.out.println(speed);
        } else if(e.getSource().equals(playBack)){
            play = !play;
            if(!play)playBack.setText("|>");
            else if(play)playBack.setText("||");

        } else if(e.getSource().equals(glider)){
            m.drawShape(0);
            repaintColony();

        } else if(e.getSource().equals(smallExploder)){
            m.drawShape(1);
            repaintColony();

        } else if(e.getSource().equals(exploder)){
            m.drawShape(2);
            repaintColony();

//        } else if(e.getSource().equals(gosperGliderGun)){
//            m.drawShape(3);
//            repaintColony();

        }
    }

    @Override
    public void run() {
        while(true){
            if(play){
                m.nextEpoch();
                repaintColony();
                try {
                    Thread.sleep(speed);
                } catch (InterruptedException ex) {
                    Logger.getLogger(Window.class.getName()).log(Level.SEVERE, null, ex);
                }
            }
        }
    }
}
class Colony extends Canvas {
    private Image screenImage;
    private Image screenImageDrawed;
    private Graphics screenGraphics;
    private Graphics screenGraphicsDrawed;
    private int cellSize = 10;
    private Matrix m;
    Colony(Matrix m){
        setBackground(new Color(0x999999));
        this.m = m;
        addMouseListener(new MouseAdapter(){
            public void mousePressed(MouseEvent e){
                addLife(e.getX(), e.getY());
                repaint();
            }
        });
        addMouseMotionListener(new MouseMotionAdapter(){
            public void mouseDragged(MouseEvent e){
                addLife(e.getX(), e.getY());
                repaint();
            }
        });
    }
    void addLife(int x, int y){
        x = x < 0 ? 0 : x;
        x = x > 498 ? 498 : x;
        y = y < 0 ? 0 : y;
        y = y > 498 ? 498 : y;
        
        
        x = (x + 1) / 10;
        y = (y + 1) / 10;
//        System.out.println(x + " " + y);
        m.insertLife(x, y);
    }
    public void draw(int x, int y){
        repaint();
    }
    @Override
    public void paint(Graphics g){
        Dimension d = getSize();
        screenImageDrawed = createImage(d.width, d.height);
        screenGraphicsDrawed = screenImageDrawed.getGraphics();
        screenGraphicsDrawed.setColor(getBackground());
        screenGraphicsDrawed.fillRect(0, 0, d.width, d.height);
        screenGraphicsDrawed.setColor(Color.gray);
        screenGraphicsDrawed.fillRect(0, 0, 50 * cellSize, 50 * cellSize);
        screenGraphicsDrawed.setColor(getBackground());
        for(int x = 1; x < 50; x++){
            screenGraphicsDrawed.drawLine(x * cellSize - 1, 0, x * cellSize - 1, cellSize * 50 - 1);
        }
        for(int y = 1; y < 50; y++){
            screenGraphicsDrawed.drawLine(0, y * cellSize - 1, cellSize * 50 - 1, y * cellSize - 1);
        }
        //g.drawImage(screenImageDrawed, 0, 0, null);
        screenGraphicsDrawed.setColor(Color.green);
        for(int x = 0; x < 50; x++){
            for(int y = 0; y < 50; y++){
                if(m.present[x][y]){
                    screenGraphicsDrawed.fillRect(x * cellSize, y * cellSize, cellSize - 1, cellSize - 1);
                }
            }
        }
        g.drawImage(screenImageDrawed, 0, 0, null);
    }
}